"""
配置管理模块
================

该模块负责管理读取和写入操作的各种配置参数。
"""


from typing import Any, Dict, List, Union, Optional, Callable
from .typedef import DataType, ReadOption, WriteOption, PreReaderType, PostReaderType
from .data_type_utils import normalize_data_type
from ..utils.logger import get_logger,default_logger


class ConfigManager:
    """配置管理器"""

    def __init__(self):
        """
        初始化配置管理器
        """
        pass

    @staticmethod
    def set_timeout(config: Dict[str, Any], timeout: Optional[Union[int, float]], operation_type: str = "both") -> Dict[str, Any]:
        """
        设置超时时间

        Args:
            config: 配置字典
            timeout: 超时时间（秒）
            operation_type: 操作类型 ("read", "write", "both")

        Returns:
            更新后的配置字典
        """
        logger = default_logger.getChild("ConfigManager")
        logger.debug(f"设置超时时间: {timeout}, 操作类型: {operation_type}")

        config['timeout'] = timeout
        return config

    @staticmethod
    def set_data_type(config: Dict[str, Any], data_type: Optional[Union[str, DataType]], operation_type: str = "both") -> Dict[str, Any]:
        """
        设置数据类型

        Args:
            config: 配置字典
            data_type: 数据类型
            operation_type: 操作类型 ("read", "write", "both")

        Returns:
            更新后的配置字典
        """
        logger = default_logger.getChild("ConfigManager")
        logger.debug(f"设置数据类型: {data_type}, 操作类型: {operation_type}")

        updated_config = config.copy()

        if operation_type in ["write", "both"]:
            # 写入操作使用统一的数据类型标准化函数
            updated_config['data_type'] = normalize_data_type(data_type)
        else:
            # 读取操作保持原有逻辑
            if isinstance(data_type, DataType):
                # 如果是DataType枚举类型，直接使用其值
                updated_config['data_type'] = data_type.value
            else:
                # 处理字符串类型的数据类型
                if isinstance(data_type, str):
                    # 转换为正确的大小写形式以匹配OPC UA标准
                    capitalized_type = data_type
                    if data_type.lower() == "string":
                        capitalized_type = "String"
                    elif data_type.lower() == "int16":
                        capitalized_type = "Int16"
                    elif data_type.lower() == "int32":
                        capitalized_type = "Int32"
                    elif data_type.lower() == "int64":
                        capitalized_type = "Int64"
                    elif data_type.lower() == "uint16":
                        capitalized_type = "UInt16"
                    elif data_type.lower() == "uint32":
                        capitalized_type = "UInt32"
                    elif data_type.lower() == "uint64":
                        capitalized_type = "UInt64"
                    elif data_type.lower() == "float":
                        capitalized_type = "Float"
                    elif data_type.lower() == "double":
                        capitalized_type = "Double"
                    elif data_type.lower() == "boolean":
                        capitalized_type = "Boolean"
                    elif data_type.lower() == "datetime":
                        capitalized_type = "DateTime"
                    elif data_type.lower() == "bytestring":
                        capitalized_type = "ByteString"
                    elif data_type.lower() == "xmlelement":
                        capitalized_type = "XmlElement"
                    elif data_type.lower() == "nodeid":
                        capitalized_type = "NodeId"
                    elif data_type.lower() == "expandednodeid":
                        capitalized_type = "ExpandedNodeId"
                    elif data_type.lower() == "statuscode":
                        capitalized_type = "StatusCode"
                    elif data_type.lower() == "qualifiedname":
                        capitalized_type = "QualifiedName"
                    elif data_type.lower() == "localizedtext":
                        capitalized_type = "LocalizedText"
                    elif data_type.lower() == "extensionobject":
                        capitalized_type = "ExtensionObject"
                    elif data_type.lower() == "datavalue":
                        capitalized_type = "DataValue"
                    elif data_type.lower() == "variant":
                        capitalized_type = "Variant"
                    elif data_type.lower() == "diagnosticinfo":
                        capitalized_type = "DiagnosticInfo"
                    elif data_type.lower() == "null":
                        capitalized_type = "Null"
                    elif data_type.lower() == "sbyte":
                        capitalized_type = "SByte"
                    elif data_type.lower() == "byte":
                        capitalized_type = "Byte"
                    elif data_type.lower() == "guid":
                        capitalized_type = "Guid"
                    else:
                        # 默认情况下首字母大写
                        capitalized_type = data_type.capitalize()

                    updated_config['data_type'] = capitalized_type
                else:
                    updated_config['data_type'] = data_type

        return updated_config

    @staticmethod
    def set_sync_mode(config: Dict[str, Any], sync: Optional[bool], operation_type: str = "both") -> Dict[str, Any]:
        """
        设置同步模式

        Args:
            config: 配置字典
            sync: 是否同步执行
            operation_type: 操作类型 ("read", "write", "both")

        Returns:
            更新后的配置字典
        """
        logger = default_logger.getChild("ConfigManager")
        logger.debug(f"设置同步模式: {sync}, 操作类型: {operation_type}")

        config['sync'] = sync
        return config

    @staticmethod
    def set_retry_count(config: Dict[str, Any], retry: Optional[int], operation_type: str = "both") -> Dict[str, Any]:
        """
        设置重试次数

        Args:
            config: 配置字典
            retry: 重试次数
            operation_type: 操作类型 ("read", "write", "both")

        Returns:
            更新后的配置字典
        """
        logger = default_logger.getChild("ConfigManager")
        logger.debug(f"设置重试次数: {retry}, 操作类型: {operation_type}")

        config['retry'] = retry
        return config

    @staticmethod
    def set_error_handling(config: Dict[str, Any], raise_on_error: Optional[bool], operation_type: str = "both") -> Dict[str, Any]:
        """
        设置错误处理方式

        Args:
            config: 配置字典
            raise_on_error: 错误时是否抛出异常
            operation_type: 操作类型 ("read", "write", "both")

        Returns:
            更新后的配置字典
        """
        logger = default_logger.getChild("ConfigManager")
        logger.debug(f"设置错误处理方式: {raise_on_error}, 操作类型: {operation_type}")

        config['raise_on_error'] = raise_on_error
        return config

    @staticmethod
    def set_quality_check(config: Dict[str, Any], quality_check: Optional[bool], operation_type: str = "both") -> Dict[str, Any]:
        """
        设置质量检查

        Args:
            config: 配置字典
            quality_check: 是否进行质量检查
            operation_type: 操作类型 ("read", "write", "both")

        Returns:
            更新后的配置字典
        """
        logger = default_logger.getChild("ConfigManager")
        logger.debug(f"设置质量检查: {quality_check}, 操作类型: {operation_type}")

        config['quality_check'] = quality_check
        return config

    @staticmethod
    def set_prereaders(config: Dict[str, Any], prereaders: Optional[List[PreReaderType]]) -> Dict[str, Any]:
        """
        设置预读取处理器

        Args:
            config: 配置字典
            prereaders: 预读取处理器列表

        Returns:
            更新后的配置字典
        """
        logger = default_logger.getChild("ConfigManager")
        logger.debug(f"设置预读取处理器: {prereaders}")

        if prereaders is not None:
            config['prereaders'] = prereaders
        return config

    @staticmethod
    def set_postreaders(config: Dict[str, Any], postreaders: Optional[List[PostReaderType]]) -> Dict[str, Any]:
        """
        设置后读取处理器

        Args:
            config: 配置字典
            postreaders: 后读取处理器列表

        Returns:
            更新后的配置字典
        """
        logger = default_logger.getChild("ConfigManager")
        logger.debug(f"设置后读取处理器: {postreaders}")

        if postreaders is not None:
            config['postreaders'] = postreaders
        return config

    @staticmethod
    def set_preprocessors(config: Dict[str, Any], preprocessors: Optional[List[Callable]]) -> Dict[str, Any]:
        """
        设置预处理器

        Args:
            config: 配置字典
            preprocessors: 预处理器列表

        Returns:
            更新后的配置字典
        """
        logger = default_logger.getChild("ConfigManager")
        logger.debug(f"设置预处理器: {preprocessors}")

        config['preprocessors'] = preprocessors
        return config

    @staticmethod
    def set_postprocessors(config: Dict[str, Any], postprocessors: Optional[List[Callable]]) -> Dict[str, Any]:
        """
        设置后处理器

        Args:
            config: 配置字典
            postprocessors: 后处理器列表

        Returns:
            更新后的配置字典
        """
        logger = default_logger.getChild("ConfigManager")
        logger.debug(f"设置后处理器: {postprocessors}")

        config['postprocessors'] = postprocessors
        return config

    @staticmethod
    def set_batch_size(config: Dict[str, Any], batch_size: Optional[int], operation_type: str = "both") -> Dict[str, Any]:
        """
        设置批量大小

        Args:
            config: 配置字典
            batch_size: 批量大小
            operation_type: 操作类型 ("read", "write", "both")

        Returns:
            更新后的配置字典
        """
        logger = default_logger.getChild("ConfigManager")
        logger.debug(f"设置批量大小: {batch_size}, 操作类型: {operation_type}")

        config['batch_size'] = batch_size
        return config

    @staticmethod
    def set_confirmation(config: Dict[str, Any], confirm: Optional[bool]) -> Dict[str, Any]:
        """
        设置确认模式

        Args:
            config: 配置字典
            confirm: 是否需要确认

        Returns:
            更新后的配置字典
        """
        logger = default_logger.getChild("ConfigManager")
        logger.debug(f"设置确认模式: {confirm}")

        config['confirm'] = confirm
        return config

    @staticmethod
    def set_transaction(config: Dict[str, Any], transaction: Optional[bool]) -> Dict[str, Any]:
        """
        设置事务模式

        Args:
            config: 配置字典
            transaction: 是否使用事务

        Returns:
            更新后的配置字典
        """
        logger = default_logger.getChild("ConfigManager")
        logger.debug(f"设置事务模式: {transaction}")

        config['transaction'] = transaction
        return config

    @staticmethod
    def get_config(config: Dict[str, Any]) -> Dict[str, Any]:
        """
        获取配置

        Args:
            config: 配置字典

        Returns:
            Dict[str, Any]: 配置的副本
        """
        logger = default_logger.getChild("ConfigManager")
        logger.debug("获取当前配置")

        # 返回配置的副本，防止外部修改影响内部状态
        return config.copy()

    @staticmethod
    def update_config(config: Dict[str, Any], update_dict: Dict[str, Any]) -> Dict[str, Any]:
        """
        更新配置

        Args:
            config: 配置字典
            update_dict: 要更新的配置

        Returns:
            更新后的配置字典
        """
        logger = default_logger.getChild("ConfigManager")
        logger.debug(f"更新配置: {update_dict}")

        config.update(update_dict)
        return config

    @staticmethod
    def reset() -> Dict[str, Any]:
        """重置配置为默认值

        Returns:
            默认配置字典
        """
        logger = default_logger.getChild("ConfigManager")
        logger.debug("重置配置为默认值")

        default_config = {
        }

        logger.debug("配置重置完成")
        return default_config

    @staticmethod
    def create_default_config() -> Dict[str, Any]:
        """
        创建默认配置

        Returns:
            默认配置字典
        """
        return ConfigManager.reset()